home *** CD-ROM | disk | FTP | other *** search
/ Linux Cubed Series 3: Developer Tools / Linux Cubed Series 3 - Developer Tools.iso / devel / lang / lisp / guile-ii.src / guile-ii / guile-src / libguile / eval.c < prev    next >
Encoding:
C/C++ Source or Header  |  1995-06-16  |  46.7 KB  |  2,153 lines

  1. /*    Copyright (C) 1995 Free Software Foundation, Inc.
  2.  * 
  3.  * This program is free software; you can redistribute it and/or modify
  4.  * it under the terms of the GNU General Public License as published by
  5.  * the Free Software Foundation; either version 2, or (at your option)
  6.  * any later version.
  7.  * 
  8.  * This program is distributed in the hope that it will be useful,
  9.  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  10.  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  11.  * GNU General Public License for more details.
  12.  * 
  13.  * You should have received a copy of the GNU General Public License
  14.  * along with this software; see the file COPYING.  If not, write to
  15.  * the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
  16.  *
  17.  * As a special exception, the Free Software Foundation gives permission
  18.  * for additional uses of the text contained in its release of GUILE.
  19.  *
  20.  * The exception is that, if you link the GUILE library with other files
  21.  * to produce an executable, this does not by itself cause the
  22.  * resulting executable to be covered by the GNU General Public License.
  23.  * Your use of that executable is in no way restricted on account of
  24.  * linking the GUILE library code into it.
  25.  *
  26.  * This exception does not however invalidate any other reasons why
  27.  * the executable file might be covered by the GNU General Public License.
  28.  *
  29.  * This exception applies only to the code released by the
  30.  * Free Software Foundation under the name GUILE.  If you copy
  31.  * code from other Free Software Foundation releases into a copy of
  32.  * GUILE, as the General Public License permits, the exception does
  33.  * not apply to the code that you add in this way.  To avoid misleading
  34.  * anyone as to the status of such modified files, you must delete
  35.  * this exception notice from them.
  36.  *
  37.  * If you write modifications of your own for GUILE, it is your choice
  38.  * whether to permit this exception to apply to your modifications.
  39.  * If you do not wish that, delete this exception notice.  
  40.  */
  41.  
  42.  
  43. #include <stdio.h>
  44. #include "_scm.h"
  45.  
  46.  
  47.  
  48. /* A resolved global variable reference in the CAR position
  49.  * of a list is stored (in code only) as a pointer to a pair with a 
  50.  * tag of 1.  This is called a "gloc".
  51.  */
  52.  
  53. #define GLOC_SYM(x) (CAR((x)-1L))
  54. #define GLOC_VAL(x) (CDR((x)-1L))
  55.  
  56.  
  57.  
  58. #define EVALCELLCAR(x, env) (SYMBOLP (CAR(x)) \
  59.                  ? *scm_lookupcar(x, env) \
  60.                  : scm_ceval(CAR(x), env))
  61.  
  62. #ifdef MEMOIZE_LOCALS
  63. #define EVALIMP(x, env) (ILOCP(x)?*scm_ilookup((x), env):x)
  64. #else
  65. #define EVALIMP(x, env) x
  66. #endif
  67. #define EVALCAR(x, env) (NCELLP(CAR(x))\
  68.             ? (IMP(CAR(x)) \
  69.                ? EVALIMP(CAR(x), env) \
  70.                : GLOC_VAL(CAR(x))) \
  71.             : EVALCELLCAR(x, env))
  72.  
  73. #define EXTEND_ENV scm_acons
  74.  
  75. /* This variable holds the thunk used to lookup top-level variables.
  76.  */
  77. SCM scm_top_level_lookup_thunk_var;
  78.  
  79. #ifdef MEMOIZE_LOCALS
  80. #ifdef __STDC__
  81. SCM *
  82. scm_ilookup (SCM iloc, SCM env)
  83. #else
  84. SCM *
  85. scm_ilookup (iloc, env)
  86.      SCM iloc;
  87.      SCM env;
  88. #endif
  89. {
  90.   register int ir = IFRAME (iloc);
  91.   register SCM er = env;
  92.   for (; 0 != ir; --ir)
  93.     er = CDR (er);
  94.   er = CAR (er);
  95.   for (ir = IDIST (iloc); 0 != ir; --ir)
  96.     er = CDR (er);
  97.   if (ICDRP (iloc))
  98.     return &CDR (er);
  99.   return &CAR (CDR (er));
  100. }
  101. #endif
  102.  
  103. #ifdef __STDC__
  104. SCM *
  105. scm_lookupcar (SCM vloc, SCM genv)
  106. #else
  107. SCM *
  108. scm_lookupcar (vloc, genv)
  109.      SCM vloc;
  110.      SCM genv;
  111. #endif
  112. {
  113.   SCM env = genv;
  114.   register SCM *al, fl, var = CAR (vloc);
  115. #ifdef MEMOIZE_LOCALS
  116.   register SCM iloc = ILOC00;
  117. #endif
  118.   for (; NIMP (env); env = CDR (env))
  119.     {
  120.       if (BOOL_T == scm_procedurep (CAR (env)))
  121.     break;
  122.       al = &CAR (env);
  123.       for (fl = CAR (*al); NIMP (fl); fl = CDR (fl))
  124.     {
  125.       if (NCONSP (fl))
  126.           if (fl == var)
  127.           {
  128. #ifdef MEMOIZE_LOCALS
  129.         CAR (vloc) = iloc + ICDR;
  130. #endif
  131.         return &CDR (*al);
  132.           }
  133.         else
  134.           break;
  135.       al = &CDR (*al);
  136.       if (CAR (fl) == var)
  137.         {
  138. #ifdef MEMOIZE_LOCALS
  139. #ifndef RECKLESS        /* letrec inits to SCM_UNDEFINED */
  140.           if (UNBNDP (CAR (*al)))
  141.         {
  142.           env = EOL;
  143.           goto errout;
  144.         }
  145. #endif
  146.           CAR (vloc) = iloc;
  147. #endif
  148.           return &CAR (*al);
  149.         }
  150. #ifdef MEMOIZE_LOCALS
  151.       iloc += IDINC;
  152. #endif
  153.     }
  154. #ifdef MEMOIZE_LOCALS
  155.       iloc = (~IDSTMSK) & (iloc + IFRINC);
  156. #endif
  157.     }
  158.   {
  159.     SCM top_thunk, vcell;
  160.     if (NIMP(env))
  161.       {
  162.     top_thunk = CAR(env);    /* env now refers to a top level env thunk */
  163.     env = CDR (env);
  164.       }
  165.     else
  166.       top_thunk = BOOL_F;
  167.     vcell = scm_sym2vcell (var, top_thunk, BOOL_F);
  168.     if (vcell == BOOL_F)
  169.       goto errout;
  170.     else
  171.       var = vcell;
  172.   }
  173. #ifndef RECKLESS
  174.   if (NNULLP (env) || UNBNDP (CDR (var)))
  175.     {
  176.       var = CAR (var);
  177.     errout:
  178.       scm_everr (vloc, genv, var,
  179.          (NULLP (env)
  180.           ? "unbound variable: "
  181.           : "damaged environment"),
  182.          "");
  183.     }
  184. #endif
  185.   CAR (vloc) = var + 1;
  186.   return &CDR (var);
  187. }
  188.  
  189. #ifdef __STDC__
  190. static SCM 
  191. unmemocar (SCM form, SCM env)
  192. #else
  193. static SCM 
  194. unmemocar (form, env)
  195.      SCM form;
  196.      SCM env;
  197. #endif
  198. {
  199.   register int ir;
  200.   if (IMP (form))
  201.     return form;
  202.   if (1 == TYP3 (form))
  203.     CAR (form) = GLOC_SYM (CAR (form));
  204. #ifdef MEMOIZE_LOCALS
  205.   else if (ILOCP (form))
  206.     {
  207.       for (ir = IFRAME (CAR (form)); ir != 0; --ir)
  208.     env = CDR (env);
  209.       env = CAR (CAR (env));
  210.       for (ir = IDIST (CAR (form)); ir != 0; --ir)
  211.     env = CDR (env);
  212.       CAR (form) = ICDRP (CAR (form)) ? env : CAR (env);
  213.     }
  214. #endif
  215.   return form;
  216. }
  217.  
  218. #ifdef __STDC__
  219. SCM 
  220. scm_eval_args (SCM l, SCM env)
  221. #else
  222. SCM 
  223. scm_eval_args (l, env)
  224.      SCM l;
  225.      SCM env;
  226. #endif
  227. {
  228.   SCM res = EOL, *lloc = &res;
  229.   while (NIMP (l))
  230.     {
  231.       *lloc = scm_cons (EVALCAR (l, env), EOL);
  232.       lloc = &CDR (*lloc);
  233.       l = CDR (l);
  234.     }
  235.   return res;
  236. }
  237.  
  238. /* 
  239.  * The following rewrite expressions and
  240.  * some memoized forms have different syntax 
  241.  */
  242.  
  243. static char s_expression[] = "missing or extra expression";
  244. static char s_test[] = "bad test";
  245. static char s_body[] = "bad body";
  246. static char s_bindings[] = "bad bindings";
  247. static char s_variable[] = "bad variable";
  248. static char s_clauses[] = "bad or missing clauses";
  249. static char s_formals[] = "bad formals";
  250. #define ASSYNT(_cond, _arg, _pos, _subr) if(!(_cond))scm_wta(_arg, (char *)_pos, _subr);
  251.  
  252. SCM scm_i_dot, scm_i_quote, scm_i_quasiquote, scm_i_lambda, scm_i_let,
  253.   scm_i_arrow, scm_i_else, scm_i_unquote, scm_i_uq_splicing, scm_i_apply;
  254. static char s_quasiquote[] = "quasiquote";
  255. static char s_delay[] = "delay";
  256.  
  257. #define ASRTSYNTAX(cond_, msg_) if(!(cond_))scm_wta(xorig, (msg_), what);
  258.  
  259.  
  260. #ifdef __STDC__
  261. static void 
  262. bodycheck (SCM xorig, SCM *bodyloc, char *what)
  263. #else
  264. static void 
  265. bodycheck (xorig, bodyloc, what)
  266.      SCM xorig;
  267.      SCM *bodyloc;
  268.      char *what;
  269. #endif
  270. {
  271.   ASRTSYNTAX (scm_ilength (*bodyloc) >= 1, s_expression);
  272. }
  273.  
  274.  
  275. #ifdef __STDC__
  276. SCM 
  277. scm_m_quote (SCM xorig, SCM env)
  278. #else
  279. SCM 
  280. scm_m_quote (xorig, env)
  281.      SCM xorig;
  282.      SCM env;
  283. #endif
  284. {
  285.   ASSYNT (scm_ilength (CDR (xorig)) == 1, xorig, s_expression, "quote");
  286.   return scm_cons (IM_QUOTE, CDR (xorig));
  287. }
  288.  
  289.  
  290. #ifdef __STDC__
  291. SCM 
  292. scm_m_begin (SCM xorig, SCM env)
  293. #else
  294. SCM 
  295. scm_m_begin (xorig, env)
  296.      SCM xorig;
  297.      SCM env;
  298. #endif
  299. {
  300.   ASSYNT (scm_ilength (CDR (xorig)) >= 1, xorig, s_expression, "begin");
  301.   return scm_cons (IM_BEGIN, CDR (xorig));
  302. }
  303.  
  304.  
  305. #ifdef __STDC__
  306. SCM 
  307. scm_m_if (SCM xorig, SCM env)
  308. #else
  309. SCM 
  310. scm_m_if (xorig, env)
  311.      SCM xorig;
  312.      SCM env;
  313. #endif
  314. {
  315.   int len = scm_ilength (CDR (xorig));
  316.   ASSYNT (len >= 2 && len <= 3, xorig, s_expression, "if");
  317.   return scm_cons (IM_IF, CDR (xorig));
  318. }
  319.  
  320.  
  321. #ifdef __STDC__
  322. SCM 
  323. scm_m_set (SCM xorig, SCM env)
  324. #else
  325. SCM 
  326. scm_m_set (xorig, env)
  327.      SCM xorig;
  328.      SCM env;
  329. #endif
  330. {
  331.   SCM x = CDR (xorig);
  332.   ASSYNT (2 == scm_ilength (x), xorig, s_expression, "set!");
  333.   ASSYNT (NIMP (CAR (x)) && SYMBOLP (CAR (x)),
  334.       xorig, s_variable, "set!");
  335.   return scm_cons (IM_SET, x);
  336. }
  337.  
  338.  
  339. #if 0
  340. #ifdef __STDC__
  341. SCM 
  342. scm_m_vref (SCM xorig, SCM env)
  343. #else
  344. SCM 
  345. scm_m_vref (xorig, env)
  346.      SCM xorig;
  347.      SCM env;
  348. #endif
  349. {
  350.   SCM x = CDR (xorig);
  351.   ASSYNT (1 == scm_ilength (x), xorig, s_expression, s_vref);
  352.   if (NIMP(x) && UDVARIABLEP (CAR (x)))
  353.     {
  354.       scm_everr (SCM_UNDEFINED, env, CAR(CDR(x)), s_variable,
  355.          "global variable reference");
  356.     }
  357.   ASSYNT (NIMP(x) && DEFVARIABLEP (CAR (x)),
  358.       xorig, s_variable, s_vref);
  359.   return 
  360.   return scm_cons (IM_VREF, x);
  361. }
  362.  
  363.  
  364. #ifdef __STDC__
  365. SCM 
  366. scm_m_vset (SCM xorig, SCM env)
  367. #else
  368. SCM 
  369. scm_m_vset (xorig, env)
  370.      SCM xorig;
  371.      SCM env;
  372. #endif
  373. {
  374.   SCM x = CDR (xorig);
  375.   ASSYNT (3 == scm_ilength (x), xorig, s_expression, s_vset);
  376.   ASSYNT ((   DEFVARIABLEP (CAR (x))
  377.        || UDVARIABLEP (CAR (x))),
  378.       xorig, s_variable, s_vset);
  379.   return scm_cons (IM_VSET, x);
  380. }
  381. #endif 
  382.  
  383.  
  384. #ifdef __STDC__
  385. SCM 
  386. scm_m_and (SCM xorig, SCM env)
  387. #else
  388. SCM 
  389. scm_m_and (xorig, env)
  390.      SCM xorig;
  391.      SCM env;
  392. #endif
  393. {
  394.   int len = scm_ilength (CDR (xorig));
  395.   ASSYNT (len >= 0, xorig, s_test, "and");
  396.   if (len >= 1)
  397.     return scm_cons (IM_AND, CDR (xorig));
  398.   else
  399.     return BOOL_T;
  400. }
  401.  
  402.  
  403. #ifdef __STDC__
  404. SCM 
  405. scm_m_or (SCM xorig, SCM env)
  406. #else
  407. SCM 
  408. scm_m_or (xorig, env)
  409.      SCM xorig;
  410.      SCM env;
  411. #endif
  412. {
  413.   int len = scm_ilength (CDR (xorig));
  414.   ASSYNT (len >= 0, xorig, s_test, "or");
  415.   if (len >= 1)
  416.     return scm_cons (IM_OR, CDR (xorig));
  417.   else
  418.     return BOOL_F;
  419. }
  420.  
  421.  
  422. #ifdef __STDC__
  423. SCM 
  424. scm_m_case (SCM xorig, SCM env)
  425. #else
  426. SCM 
  427. scm_m_case (xorig, env)
  428.      SCM xorig;
  429.      SCM env;
  430. #endif
  431. {
  432.   SCM proc, x = CDR (xorig);
  433.   ASSYNT (scm_ilength (x) >= 2, xorig, s_clauses, "case");
  434.   while (NIMP (x = CDR (x)))
  435.     {
  436.       proc = CAR (x);
  437.       ASSYNT (scm_ilength (proc) >= 2, xorig, s_clauses, "case");
  438.       ASSYNT (scm_ilength (CAR (proc)) >= 0 || scm_i_else == CAR (proc),
  439.           xorig, s_clauses, "case");
  440.     }
  441.   return scm_cons (IM_CASE, CDR (xorig));
  442. }
  443.  
  444.  
  445. #ifdef __STDC__
  446. SCM 
  447. scm_m_cond (SCM xorig, SCM env)
  448. #else
  449. SCM 
  450. scm_m_cond (xorig, env)
  451.      SCM xorig;
  452.      SCM env;
  453. #endif
  454. {
  455.   SCM arg1, x = CDR (xorig);
  456.   int len = scm_ilength (x);
  457.   ASSYNT (len >= 1, xorig, s_clauses, "cond");
  458.   while (NIMP (x))
  459.     {
  460.       arg1 = CAR (x);
  461.       len = scm_ilength (arg1);
  462.       ASSYNT (len >= 1, xorig, s_clauses, "cond");
  463.       if (scm_i_else == CAR (arg1))
  464.     {
  465.       ASSYNT (NULLP (CDR (x)) && len >= 2, xorig, "bad ELSE clause", "cond");
  466.       CAR (arg1) = BOOL_T;
  467.     }
  468.       if (len >= 2 && scm_i_arrow == CAR (CDR (arg1)))
  469.     ASSYNT (3 == len && NIMP (CAR (CDR (CDR (arg1)))),
  470.         xorig, "bad recipient", "cond");
  471.       x = CDR (x);
  472.     }
  473.   return scm_cons (IM_COND, CDR (xorig));
  474. }
  475.  
  476.  
  477. #ifdef __STDC__
  478. SCM 
  479. scm_m_lambda (SCM xorig, SCM env)
  480. #else
  481. SCM 
  482. scm_m_lambda (xorig, env)
  483.      SCM xorig;
  484.      SCM env;
  485. #endif
  486. {
  487.   SCM proc, x = CDR (xorig);
  488.   if (scm_ilength (x) < 2)
  489.     goto badforms;
  490.   proc = CAR (x);
  491.   if NULLP
  492.     (proc) goto memlambda;
  493.   if IMP
  494.     (proc) goto badforms;
  495.   if SYMBOLP
  496.     (proc) goto memlambda;
  497.   if NCONSP
  498.     (proc) goto badforms;
  499.   while NIMP
  500.     (proc)
  501.     {
  502.       if NCONSP
  503.     (proc)
  504.       if (!SYMBOLP (proc))
  505.       goto badforms;
  506.     else
  507.       goto memlambda;
  508.       if (!(NIMP (CAR (proc)) && SYMBOLP (CAR (proc))))
  509.     goto badforms;
  510.       proc = CDR (proc);
  511.     }
  512.   if NNULLP
  513.     (proc)
  514.   badforms:scm_wta (xorig, s_formals, "lambda");
  515. memlambda:
  516.   bodycheck (xorig, &CDR (x), "lambda");
  517.   return scm_cons (IM_LAMBDA, CDR (xorig));
  518. }
  519.  
  520.  
  521. #ifdef __STDC__
  522. SCM 
  523. scm_m_letstar (SCM xorig, SCM env)
  524. #else
  525. SCM 
  526. scm_m_letstar (xorig, env)
  527.      SCM xorig;
  528.      SCM env;
  529. #endif
  530. {
  531.   SCM x = CDR (xorig), arg1, proc, vars = EOL, *varloc = &vars;
  532.   int len = scm_ilength (x);
  533.   ASSYNT (len >= 2, xorig, s_body, "let*");
  534.   proc = CAR (x);
  535.   ASSYNT (scm_ilength (proc) >= 0, xorig, s_bindings, "let*");
  536.   while NIMP
  537.     (proc)
  538.     {
  539.       arg1 = CAR (proc);
  540.       ASSYNT (2 == scm_ilength (arg1), xorig, s_bindings, "let*");
  541.       ASSYNT (NIMP (CAR (arg1)) && SYMBOLP (CAR (arg1)), xorig, s_variable, "let*");
  542.       *varloc = scm_cons2 (CAR (arg1), CAR (CDR (arg1)), EOL);
  543.       varloc = &CDR (CDR (*varloc));
  544.       proc = CDR (proc);
  545.     }
  546.   x = scm_cons (vars, CDR (x));
  547.   bodycheck (xorig, &CDR (x), "let*");
  548.   return scm_cons (IM_LETSTAR, x);
  549. }
  550.  
  551. /* DO gets the most radically altered syntax
  552.    (do ((<var1> <init1> <step1>)
  553.    (<var2> <init2>)
  554.    ... )
  555.    (<test> <return>)
  556.    <body>)
  557.    ;; becomes
  558.    (do_mem (varn ... var2 var1)
  559.    (<init1> <init2> ... <initn>)
  560.    (<test> <return>)
  561.    (<body>)
  562.    <step1> <step2> ... <stepn>) ;; missing steps replaced by var
  563.    */
  564.  
  565.  
  566. #ifdef __STDC__
  567. SCM 
  568. scm_m_do (SCM xorig, SCM env)
  569. #else
  570. SCM 
  571. scm_m_do (xorig, env)
  572.      SCM xorig;
  573.      SCM env;
  574. #endif
  575. {
  576.   SCM x = CDR (xorig), arg1, proc;
  577.   SCM vars = EOL, inits = EOL, steps = EOL;
  578.   SCM *initloc = &inits, *steploc = &steps;
  579.   int len = scm_ilength (x);
  580.   ASSYNT (len >= 2, xorig, s_test, "do");
  581.   proc = CAR (x);
  582.   ASSYNT (scm_ilength (proc) >= 0, xorig, s_bindings, "do");
  583.   while NIMP
  584.     (proc)
  585.     {
  586.       arg1 = CAR (proc);
  587.       len = scm_ilength (arg1);
  588.       ASSYNT (2 == len || 3 == len, xorig, s_bindings, "do");
  589.       ASSYNT (NIMP (CAR (arg1)) && SYMBOLP (CAR (arg1)), xorig, s_variable, "do");
  590.       /* vars reversed here, inits and steps reversed at evaluation */
  591.       vars = scm_cons (CAR (arg1), vars);    /* variable */
  592.       arg1 = CDR (arg1);
  593.       *initloc = scm_cons (CAR (arg1), EOL);    /* init */
  594.       initloc = &CDR (*initloc);
  595.       arg1 = CDR (arg1);
  596.       *steploc = scm_cons (IMP (arg1) ? CAR (vars) : CAR (arg1), EOL);    /* step */
  597.       steploc = &CDR (*steploc);
  598.       proc = CDR (proc);
  599.     }
  600.   x = CDR (x);
  601.   ASSYNT (scm_ilength (CAR (x)) >= 1, xorig, s_test, "do");
  602.   x = scm_cons2 (CAR (x), CDR (x), steps);
  603.   x = scm_cons2 (vars, inits, x);
  604.   bodycheck (xorig, &CAR (CDR (CDR (x))), "do");
  605.   return scm_cons (IM_DO, x);
  606. }
  607.  
  608. /* evalcar is small version of inline EVALCAR when we don't care about speed */
  609. #ifdef __STDC__
  610. static SCM 
  611. evalcar (SCM x, SCM env)
  612. #else
  613. static SCM 
  614. evalcar (x, env)
  615.      SCM x;
  616.      SCM env;
  617. #endif
  618. {
  619.   return EVALCAR (x, env);
  620. }
  621.  
  622. #ifdef __STDC__
  623. static SCM 
  624. iqq (SCM form, SCM env, int depth)
  625. #else
  626. static SCM 
  627. iqq (form, env, depth)
  628.      SCM form;
  629.      SCM env;
  630.      int depth;
  631. #endif
  632. {
  633.   SCM tmp;
  634.   int edepth = depth;
  635.   if IMP
  636.     (form) return form;
  637.   if VECTORP
  638.     (form)
  639.     {
  640.       long i = LENGTH (form);
  641.       SCM *data = VELTS (form);
  642.       tmp = EOL;
  643.       for (; --i >= 0;)
  644.     tmp = scm_cons (data[i], tmp);
  645.       return scm_vector (iqq (tmp, env, depth));
  646.     }
  647.   if NCONSP
  648.     (form) return form;
  649.   tmp = CAR (form);
  650.   if (scm_i_quasiquote == tmp)
  651.     {
  652.       depth++;
  653.       goto label;
  654.     }
  655.   if (scm_i_unquote == tmp)
  656.     {
  657.       --depth;
  658.     label:
  659.       form = CDR (form);
  660.       ASSERT (NIMP (form) && ECONSP (form) && NULLP (CDR (form)),
  661.           form, ARG1, s_quasiquote);
  662.       if (0 == depth)
  663.     return evalcar (form, env);
  664.       return scm_cons2 (tmp, iqq (CAR (form), env, depth), EOL);
  665.     }
  666.   if (NIMP (tmp) && (scm_i_uq_splicing == CAR (tmp)))
  667.     {
  668.       tmp = CDR (tmp);
  669.       if (0 == --edepth)
  670.     return scm_append (scm_cons2 (evalcar (tmp, env), iqq (CDR (form), env, depth), EOL));
  671.     }
  672.   return scm_cons (iqq (CAR (form), env, edepth), iqq (CDR (form), env, depth));
  673. }
  674.  
  675. /* Here are acros which return values rather than code. */
  676.  
  677. #ifdef __STDC__
  678. SCM 
  679. scm_m_quasiquote (SCM xorig, SCM env)
  680. #else
  681. SCM 
  682. scm_m_quasiquote (xorig, env)
  683.      SCM xorig;
  684.      SCM env;
  685. #endif
  686. {
  687.   SCM x = CDR (xorig);
  688.   ASSYNT (scm_ilength (x) == 1, xorig, s_expression, s_quasiquote);
  689.   return iqq (CAR (x), env, 1);
  690. }
  691.  
  692. #ifdef __STDC__
  693. SCM 
  694. scm_m_delay (SCM xorig, SCM env)
  695. #else
  696. SCM 
  697. scm_m_delay (xorig, env)
  698.      SCM xorig;
  699.      SCM env;
  700. #endif
  701. {
  702.   ASSYNT (scm_ilength (xorig) == 2, xorig, s_expression, s_delay);
  703.   xorig = CDR (xorig);
  704.   return scm_makprom (scm_closure (scm_cons2 (EOL, CAR (xorig), CDR (xorig)),
  705.                    env));
  706. }
  707.  
  708. #ifdef __STDC__
  709. static SCM
  710. env_top_level (SCM env)
  711. #else
  712. static SCM
  713. env_top_level (env)
  714.      SCM env;
  715. #endif
  716. {
  717.   while (NIMP(env))
  718.     {
  719.       if (BOOL_T == scm_procedurep (CAR(env)))
  720.     return CAR(env);
  721.       env = CDR (env);
  722.     }
  723.   return BOOL_F;
  724. }
  725.  
  726. extern int scm_verbose;
  727. #ifdef __STDC__
  728. SCM 
  729. scm_m_define (SCM x, SCM env)
  730. #else
  731. SCM 
  732. scm_m_define (x, env)
  733.      SCM x;
  734.      SCM env;
  735. #endif
  736. {
  737.   SCM proc, arg1 = x;
  738.   x = CDR (x);
  739.   /*  ASSYNT(NULLP(env), x, "bad placement", s_define);*/
  740.   ASSYNT (scm_ilength (x) >= 2, arg1, s_expression, "define");
  741.   proc = CAR (x);
  742.   x = CDR (x);
  743.   while (NIMP (proc) && CONSP (proc))
  744.     {                /* nested define syntax */
  745.       x = scm_cons (scm_cons2 (scm_i_lambda, CDR (proc), x), EOL);
  746.       proc = CAR (proc);
  747.     }
  748.   ASSYNT (NIMP (proc) && SYMBOLP (proc), arg1, s_variable, "define");
  749.   ASSYNT (1 == scm_ilength (x), arg1, s_expression, "define");
  750.   if (TOP_LEVEL (env))
  751.     {
  752.       x = evalcar (x, env);
  753.       arg1 = scm_sym2vcell (proc, env_top_level (env), BOOL_T);
  754. #ifndef RECKLESS
  755.       if (NIMP (CDR (arg1)) && ((SCM) SNAME (CDR (arg1)) == proc)
  756.       && (CDR (arg1) != x))
  757.     scm_warn ("redefining built-in ", CHARS (proc));
  758.       else
  759. #endif
  760.       if (5 <= scm_verbose && SCM_UNDEFINED != CDR (arg1))
  761.     scm_warn ("redefining ", CHARS (proc));
  762.       CDR (arg1) = x;
  763. #ifdef SICP
  764.       return scm_cons2 (scm_i_quote, CAR (arg1), EOL);
  765. #else
  766.       return UNSPECIFIED;
  767. #endif
  768.     }
  769.   return scm_cons2 (IM_DEFINE, proc, x);
  770. }
  771. /* end of acros */
  772.  
  773. #ifdef __STDC__
  774. SCM 
  775. scm_m_letrec (SCM xorig, SCM env)
  776. #else
  777. SCM 
  778. scm_m_letrec (xorig, env)
  779.      SCM xorig;
  780.      SCM env;
  781. #endif
  782. {
  783.   SCM cdrx = CDR (xorig);    /* locally mutable version of form */
  784.   char *what = CHARS (CAR (xorig));
  785.   SCM x = cdrx, proc, arg1;    /* structure traversers */
  786.   SCM vars = EOL, inits = EOL, *initloc = &inits;
  787.  
  788.   ASRTSYNTAX (scm_ilength (x) >= 2, s_body);
  789.   proc = CAR (x);
  790.   if NULLP
  791.     (proc) return scm_m_letstar (xorig, env);    /* null binding, let* faster */
  792.   ASRTSYNTAX (scm_ilength (proc) >= 1, s_bindings);
  793.   do
  794.     {
  795.       /* vars scm_list reversed here, inits reversed at evaluation */
  796.       arg1 = CAR (proc);
  797.       ASRTSYNTAX (2 == scm_ilength (arg1), s_bindings);
  798.       ASRTSYNTAX (NIMP (CAR (arg1)) && SYMBOLP (CAR (arg1)), s_variable);
  799.       vars = scm_cons (CAR (arg1), vars);
  800.       *initloc = scm_cons (CAR (CDR (arg1)), EOL);
  801.       initloc = &CDR (*initloc);
  802.     }
  803.   while NIMP
  804.   (proc = CDR (proc));
  805.   cdrx = scm_cons2 (vars, inits, CDR (x));
  806.   bodycheck (xorig, &CDR (CDR (cdrx)), what);
  807.   return scm_cons (IM_LETREC, cdrx);
  808. }
  809.  
  810. #ifdef __STDC__
  811. SCM 
  812. scm_m_let (SCM xorig, SCM env)
  813. #else
  814. SCM 
  815. scm_m_let (xorig, env)
  816.      SCM xorig;
  817.      SCM env;
  818. #endif
  819. {
  820.   SCM cdrx = CDR (xorig);    /* locally mutable version of form */
  821.   SCM x = cdrx, proc, arg1, name;    /* structure traversers */
  822.   SCM vars = EOL, inits = EOL, *varloc = &vars, *initloc = &inits;
  823.  
  824.   ASSYNT (scm_ilength (x) >= 2, xorig, s_body, "let");
  825.   proc = CAR (x);
  826.   if (NULLP (proc)
  827.       || (NIMP (proc) && CONSP (proc)
  828.       && NIMP (CAR (proc)) && CONSP (CAR (proc)) && NULLP (CDR (proc))))
  829.     return scm_m_letstar (xorig, env);    /* null or single binding, let* is faster */
  830.   ASSYNT (NIMP (proc), xorig, s_bindings, "let");
  831.   if (CONSP (proc))            /* plain let, proc is <bindings> */
  832.       return scm_cons (IM_LET, CDR (scm_m_letrec (xorig, env)));
  833.   if (!SYMBOLP (proc))
  834.     scm_wta (xorig, s_bindings, "let");    /* bad let */
  835.   name = proc;            /* named let, build equiv letrec */
  836.   x = CDR (x);
  837.   ASSYNT (scm_ilength (x) >= 2, xorig, s_body, "let");
  838.   proc = CAR (x);        /* bindings scm_list */
  839.   ASSYNT (scm_ilength (proc) >= 0, xorig, s_bindings, "let");
  840.   while NIMP
  841.     (proc)
  842.     {                /* vars and inits both in order */
  843.       arg1 = CAR (proc);
  844.       ASSYNT (2 == scm_ilength (arg1), xorig, s_bindings, "let");
  845.       ASSYNT (NIMP (CAR (arg1)) && SYMBOLP (CAR (arg1)), xorig, s_variable, "let");
  846.       *varloc = scm_cons (CAR (arg1), EOL);
  847.       varloc = &CDR (*varloc);
  848.       *initloc = scm_cons (CAR (CDR (arg1)), EOL);
  849.       initloc = &CDR (*initloc);
  850.       proc = CDR (proc);
  851.     }
  852.   return
  853.     scm_m_letrec (scm_cons2 (scm_i_let,
  854.                  scm_cons (scm_cons2 (name, scm_cons2 (scm_i_lambda, vars, CDR (x)), EOL), EOL),
  855.                  scm_acons (name, inits, EOL)),     /* body */
  856.           env);
  857. }
  858.  
  859. #define s_atapply (ISYMCHARS(IM_APPLY)+1)
  860.  
  861. #ifdef __STDC__
  862. SCM 
  863. scm_m_apply (SCM xorig, SCM env)
  864. #else
  865. SCM 
  866. scm_m_apply (xorig, env)
  867.      SCM xorig;
  868.      SCM env;
  869. #endif
  870. {
  871.   ASSYNT (scm_ilength (CDR (xorig)) == 2, xorig, s_expression, "@apply");
  872.   return scm_cons (IM_APPLY, CDR (xorig));
  873. }
  874.  
  875. #define s_atcall_cc (ISYMCHARS(IM_CONT)+1)
  876.  
  877. #ifdef __STDC__
  878. SCM 
  879. scm_m_cont (SCM xorig, SCM env)
  880. #else
  881. SCM 
  882. scm_m_cont (xorig, env)
  883.      SCM xorig;
  884.      SCM env;
  885. #endif
  886. {
  887.   ASSYNT (scm_ilength (CDR (xorig)) == 1, xorig, s_expression, "@call-with-current-continuation");
  888.   return scm_cons (IM_CONT, CDR (xorig));
  889. }
  890.  
  891. #ifndef RECKLESS
  892. #ifdef __STDC__
  893. int 
  894. scm_badargsp (SCM formals, SCM args)
  895. #else
  896. int 
  897. scm_badargsp (formals, args)
  898.      SCM formals;
  899.      SCM args;
  900. #endif
  901. {
  902.   while NIMP
  903.     (formals)
  904.     {
  905.       if NCONSP
  906.     (formals) return 0;
  907.       if IMP
  908.     (args) return 1;
  909.       formals = CDR (formals);
  910.       args = CDR (args);
  911.     }
  912.   return NNULLP (args) ? 1 : 0;
  913. }
  914. #endif
  915.  
  916.  
  917.  
  918. static char scm_s_map[];
  919. static char scm_s_for_each[];
  920. long scm_tc16_macro;
  921.  
  922. #ifdef __STDC__
  923. SCM 
  924. scm_ceval (SCM x, SCM env)
  925. #else
  926. SCM 
  927. scm_ceval (x, env)
  928.      SCM x;
  929.      SCM env;
  930. #endif
  931. {
  932.   union
  933.     {
  934.       SCM *lloc;
  935.       SCM arg1;
  936.     } t;
  937.   SCM proc, arg2;
  938.   CHECK_STACK;
  939. loop:POLL;
  940.   switch (TYP7 (x))
  941.     {
  942.     case tcs_symbols:
  943.       /* only happens when called at top level */
  944.       x = scm_cons (x, SCM_UNDEFINED);
  945.       goto retval;
  946.     case (127 & IM_AND):
  947.       x = CDR (x);
  948.       t.arg1 = x;
  949.       while (NNULLP (t.arg1 = CDR (t.arg1)))
  950.     if FALSEP (EVALCAR (x, env)) return BOOL_F;
  951.     else
  952.       x = t.arg1;
  953.       goto carloop;
  954.     case (127 & IM_BEGIN):
  955.     cdrxbegin:
  956.       x = CDR (x);
  957.     begin:
  958.       t.arg1 = x;
  959.       while (NNULLP (t.arg1 = CDR (t.arg1)))
  960.     {
  961.       SIDEVAL (CAR (x), env);
  962.       x = t.arg1;
  963.     }
  964.     carloop:            /* scm_eval car of last form in scm_list */
  965.       if (NCELLP (CAR (x)))
  966.     {
  967.       x = CAR (x);
  968.       return IMP (x) ? EVALIMP (x, env) : GLOC_VAL (x);
  969.     }
  970.       if (SYMBOLP (CAR (x)))
  971.     {
  972.     retval:
  973.       return *scm_lookupcar (x, env);
  974.     }
  975.       x = CAR (x);
  976.       goto loop;        /* tail recurse */
  977.  
  978.     case (127 & IM_CASE):
  979.       x = CDR (x);
  980.       t.arg1 = EVALCAR (x, env);
  981.       while (NIMP (x = CDR (x)))
  982.     {
  983.       proc = CAR (x);
  984.       if (scm_i_else == CAR (proc))
  985.         {
  986.           x = CDR (proc);
  987.           goto begin;
  988.         }
  989.       proc = CAR (proc);
  990.       while (NIMP (proc))
  991.         {
  992.           if (CAR (proc) == t.arg1
  993. #ifdef FLOATS
  994.           || NFALSEP (scm_eqv_p (CAR (proc), t.arg1))
  995. #endif
  996.         )
  997.         {
  998.           x = CDR (CAR (x));
  999.           goto begin;
  1000.         }
  1001.           proc = CDR (proc);
  1002.         }
  1003.     }
  1004.       return UNSPECIFIED;
  1005.     case (127 & IM_COND):
  1006.       while (NIMP (x = CDR (x)))
  1007.     {
  1008.       proc = CAR (x);
  1009.       t.arg1 = EVALCAR (proc, env);
  1010.       if NFALSEP
  1011.         (t.arg1)
  1012.         {
  1013.           x = CDR (proc);
  1014.           if NULLP
  1015.         (x) return t.arg1;
  1016.           if (scm_i_arrow != CAR (x))
  1017.         goto begin;
  1018.           proc = CDR (x);
  1019.           proc = EVALCAR (proc, env);
  1020.           ASRTGO (NIMP (proc), badfun);
  1021.           goto evap1;
  1022.         }
  1023.     }
  1024.       return UNSPECIFIED;
  1025.     case (127 & IM_DO):
  1026.       x = CDR (x);
  1027.       proc = CAR (CDR (x));    /* inits */
  1028.       t.arg1 = EOL;        /* values */
  1029.       while (NIMP (proc))
  1030.     {
  1031.       t.arg1 = scm_cons (EVALCAR (proc, env), t.arg1);
  1032.       proc = CDR (proc);
  1033.     }
  1034.       env = EXTEND_ENV (CAR (x), t.arg1, env);
  1035.       x = CDR (CDR (x));
  1036.       while (proc = CAR (x), FALSEP (EVALCAR (proc, env)))
  1037.     {
  1038.       for (proc = CAR (CDR (x)); NIMP (proc); proc = CDR (proc))
  1039.         {
  1040.           t.arg1 = CAR (proc);    /* body */
  1041.           SIDEVAL (t.arg1, env);
  1042.         }
  1043.       for (t.arg1 = EOL, proc = CDR (CDR (x)); NIMP (proc); proc = CDR (proc))
  1044.         t.arg1 = scm_cons (EVALCAR (proc, env), t.arg1);    /* steps */
  1045.       env = EXTEND_ENV (CAR (CAR (env)), t.arg1, CDR (env));
  1046.     }
  1047.       x = CDR (proc);
  1048.       if NULLP (x)
  1049.     return UNSPECIFIED;
  1050.       goto begin;
  1051.     case (127 & IM_IF):
  1052.       x = CDR (x);
  1053.       if NFALSEP
  1054.     (EVALCAR (x, env)) x = CDR (x);
  1055.       else if IMP
  1056.     (x = CDR (CDR (x))) return UNSPECIFIED;
  1057.       goto carloop;
  1058.     case (127 & IM_LET):
  1059.       x = CDR (x);
  1060.       proc = CAR (CDR (x));
  1061.       t.arg1 = EOL;
  1062.       do
  1063.     {
  1064.       t.arg1 = scm_cons (EVALCAR (proc, env), t.arg1);
  1065.     }
  1066.       while NIMP
  1067.       (proc = CDR (proc));
  1068.       env = EXTEND_ENV (CAR (x), t.arg1, env);
  1069.       x = CDR (x);
  1070.       goto cdrxbegin;
  1071.     case (127 & IM_LETREC):
  1072.       x = CDR (x);
  1073.       env = EXTEND_ENV (CAR (x), undefineds, env);
  1074.       x = CDR (x);
  1075.       proc = CAR (x);
  1076.       t.arg1 = EOL;
  1077.       do
  1078.     {
  1079.       t.arg1 = scm_cons (EVALCAR (proc, env), t.arg1);
  1080.     }
  1081.       while NIMP
  1082.       (proc = CDR (proc));
  1083.       CDR (CAR (env)) = t.arg1;
  1084.       goto cdrxbegin;
  1085.     case (127 & IM_LETSTAR):
  1086.       x = CDR (x);
  1087.       proc = CAR (x);
  1088.       if IMP
  1089.     (proc)
  1090.     {
  1091.       env = EXTEND_ENV (EOL, EOL, env);
  1092.       goto cdrxbegin;
  1093.     }
  1094.       do
  1095.     {
  1096.       t.arg1 = CAR (proc);
  1097.       proc = CDR (proc);
  1098.       env = EXTEND_ENV (t.arg1, EVALCAR (proc, env), env);
  1099.     }
  1100.       while NIMP
  1101.       (proc = CDR (proc));
  1102.       goto cdrxbegin;
  1103.     case (127 & IM_OR):
  1104.       x = CDR (x);
  1105.       t.arg1 = x;
  1106.       while (NNULLP (t.arg1 = CDR (t.arg1)))
  1107.     {
  1108.       x = EVALCAR (x, env);
  1109.       if NFALSEP
  1110.         (x) return x;
  1111.       x = t.arg1;
  1112.     }
  1113.       goto carloop;
  1114.     case (127 & IM_LAMBDA):
  1115.       return scm_closure (CDR (x), env);
  1116.     case (127 & IM_QUOTE):
  1117.       return CAR (CDR (x));
  1118.     case (127 & IM_SET):
  1119.       x = CDR (x);
  1120.       proc = CAR (x);
  1121.       switch (7 & (int) proc)
  1122.     {
  1123.     case 0:
  1124.       t.lloc = scm_lookupcar (x, env);
  1125.       break;
  1126.     case 1:
  1127.       t.lloc = &GLOC_VAL (proc);
  1128.       break;
  1129. #ifdef MEMOIZE_LOCALS
  1130.     case 4:
  1131.       t.lloc = scm_ilookup (proc, env);
  1132.       break;
  1133. #endif
  1134.     }
  1135.       x = CDR (x);
  1136.       *t.lloc = EVALCAR (x, env);
  1137. #ifdef SICP
  1138.       return *t.lloc;
  1139. #else
  1140.       return UNSPECIFIED;
  1141. #endif
  1142.     case (127 & IM_DEFINE):    /* only for internal defines */
  1143.       x = CDR (x);
  1144.       proc = CAR (x);
  1145.       x = CDR (x);
  1146.       x = evalcar (x, env);
  1147.       env = CAR (env);
  1148.       DEFER_INTS;
  1149.       CAR (env) = scm_cons (proc, CAR (env));
  1150.       CDR (env) = scm_cons (x, CDR (env));
  1151.       ALLOW_INTS;
  1152.       return UNSPECIFIED;
  1153.       /* new syntactic forms go here. */
  1154.     case (127 & MAKISYM (0)):
  1155.       proc = CAR (x);
  1156.       ASRTGO (ISYMP (proc), badfun);
  1157.       switch ISYMNUM (proc)
  1158.     {
  1159. #if 0
  1160.     case (ISYMNUM (IM_VREF)):
  1161.       {
  1162.         SCM var;
  1163.         var = CAR (CDR (x));
  1164.         return CDR(var);
  1165.       }
  1166.     case (ISYMNUM (IM_VSET)):
  1167.       CDR (CAR ( CDR (x))) = EVALCAR( CDR ( CDR (x)), env);
  1168.       CAR (CAR ( CDR (x))) = scm_tc16_variable;
  1169.       return UNSPECIFIED;
  1170. #endif
  1171.     case (ISYMNUM (IM_APPLY)):
  1172.       proc = CDR (x);
  1173.       proc = EVALCAR (proc, env);
  1174.       ASRTGO (NIMP (proc), badfun);
  1175.       if (CLOSUREP (proc))
  1176.         {
  1177.           t.arg1 = CDR (CDR (x));
  1178.           t.arg1 = EVALCAR (t.arg1, env);
  1179. #ifndef RECKLESS
  1180.           if (scm_badargsp (CAR (CODE (proc)), t.arg1))
  1181.         goto wrongnumargs;
  1182. #endif
  1183.           env = EXTEND_ENV (CAR (CODE (proc)), t.arg1, ENV (proc));
  1184.           x = CODE (proc);
  1185.           goto cdrxbegin;
  1186.         }
  1187.       proc = scm_i_apply;
  1188.       goto evapply;
  1189.     case (ISYMNUM (IM_CONT)):
  1190.       t.arg1 = scm_make_cont ();
  1191.       if (setjmp (JMPBUF (t.arg1)))
  1192.         return scm_throwval;
  1193.       proc = CDR (x);
  1194.       proc = evalcar (proc, env);
  1195.       ASRTGO (NIMP (proc), badfun);
  1196.       goto evap1;
  1197.     default:
  1198.       goto badfun;
  1199.     }
  1200.     default:
  1201.       proc = x;
  1202.     badfun:
  1203.       scm_everr (x, env, proc, "Wrong type to apply: ", "");
  1204.     case tc7_vector:
  1205.     case tc7_bvect:
  1206.     case tc7_ivect:
  1207.     case tc7_uvect:
  1208.     case tc7_fvect:
  1209.     case tc7_dvect:
  1210.     case tc7_cvect:
  1211.     case tc7_string:
  1212.     case tc7_smob:
  1213.     case tcs_closures:
  1214.     case tcs_subrs:
  1215.       return x;
  1216. #ifdef MEMOIZE_LOCALS
  1217.     case (127 & ILOC00):
  1218.       proc = *scm_ilookup (CAR (x), env);
  1219.       ASRTGO (NIMP (proc), badfun);
  1220. #ifndef RECKLESS
  1221. #ifdef CAUTIOUS
  1222.       goto checkargs;
  1223. #endif
  1224. #endif
  1225.       break;
  1226. #endif /* ifdef MEMOIZE_LOCALS */
  1227.     case tcs_cons_gloc:
  1228.       proc = GLOC_VAL (CAR (x));
  1229.       ASRTGO (NIMP (proc), badfun);
  1230. #ifndef RECKLESS
  1231. #ifdef CAUTIOUS
  1232.       goto checkargs;
  1233. #endif
  1234. #endif
  1235.       break;
  1236.     case tcs_cons_nimcar:
  1237.       if (SYMBOLP (CAR (x)))
  1238.     {
  1239.       proc = *scm_lookupcar (x, env);
  1240.       if (IMP (proc))
  1241.         {
  1242.           unmemocar (x, env);
  1243.           goto badfun;
  1244.         }
  1245.       if (scm_tc16_macro == TYP16 (proc))
  1246.         {
  1247.           unmemocar (x, env);
  1248.           t.arg1 = scm_apply (CDR (proc), x, scm_cons (env, listofnull));
  1249.           switch ((int) (CAR (proc) >> 16))
  1250.         {
  1251.         case 2:
  1252.           if (scm_ilength (t.arg1) <= 0)
  1253.             t.arg1 = scm_cons2 (IM_BEGIN, t.arg1, EOL);
  1254.           DEFER_INTS;
  1255.           CAR (x) = CAR (t.arg1);
  1256.           CDR (x) = CDR (t.arg1);
  1257.           ALLOW_INTS;
  1258.           goto loop;
  1259.         case 1:
  1260.           if (NIMP (x = t.arg1))
  1261.             goto loop;
  1262.         case 0:
  1263.           return t.arg1;
  1264.         }
  1265.         }
  1266.     }
  1267.       else
  1268.     proc = scm_ceval (CAR (x), env);
  1269.       ASRTGO (NIMP (proc), badfun);
  1270. #ifndef RECKLESS
  1271. #ifdef CAUTIOUS
  1272.     checkargs:
  1273. #endif
  1274.       if (CLOSUREP (proc))
  1275.     {
  1276.       arg2 = CAR (CODE (proc));
  1277.       t.arg1 = CDR (x);
  1278.       while (NIMP (arg2))
  1279.         {
  1280.           if (NCONSP (arg2))
  1281.           goto evapply;
  1282.           if (IMP (t.arg1))
  1283.         goto umwrongnumargs;
  1284.           arg2 = CDR (arg2);
  1285.           t.arg1 = CDR (t.arg1);
  1286.         }
  1287.       if (NNULLP (t.arg1))
  1288.         goto umwrongnumargs;
  1289.     }
  1290. #endif
  1291.     }
  1292. evapply:
  1293.   if (NULLP (CDR (x)))
  1294.     switch (TYP7 (proc))
  1295.       {                /* no arguments given */
  1296.       case tc7_subr_0:
  1297.     return SUBRF (proc) ();
  1298.       case tc7_subr_1o:
  1299.     return SUBRF (proc) (SCM_UNDEFINED);
  1300.       case tc7_lsubr:
  1301.     return SUBRF (proc) (EOL);
  1302.       case tc7_rpsubr:
  1303.     return BOOL_T;
  1304.       case tc7_asubr:
  1305.     return SUBRF (proc) (SCM_UNDEFINED, SCM_UNDEFINED);
  1306. #ifdef CCLO
  1307.       case tc7_cclo:
  1308.     t.arg1 = proc;
  1309.     proc = CCLO_SUBR (proc);
  1310.     goto evap1;
  1311. #endif
  1312.       case tcs_closures:
  1313.     x = CODE (proc);
  1314.     env = EXTEND_ENV (CAR (x), EOL, ENV (proc));
  1315.     goto cdrxbegin;
  1316.       case tc7_contin:
  1317.       case tc7_subr_1:
  1318.       case tc7_subr_2:
  1319.       case tc7_subr_2o:
  1320.       case tc7_cxr:
  1321.       case tc7_subr_3:
  1322.       case tc7_lsubr_2:
  1323.       umwrongnumargs:
  1324.     unmemocar (x, env);
  1325.       wrongnumargs:
  1326.     scm_everr (x, env, proc, (char *) WNA, "");
  1327.       default:
  1328.     goto badfun;
  1329.       }
  1330.   x = CDR (x);
  1331. #ifdef CAUTIOUS
  1332.   if (IMP (x))
  1333.     goto wrongnumargs;
  1334. #endif
  1335.   t.arg1 = EVALCAR (x, env);
  1336.   x = CDR (x);
  1337.   if (NULLP (x))
  1338.   evap1:
  1339.     switch (TYP7 (proc))
  1340.       {                /* have one argument in t.arg1 */
  1341.       case tc7_subr_2o:
  1342.     return SUBRF (proc) (t.arg1, SCM_UNDEFINED);
  1343.       case tc7_subr_1:
  1344.       case tc7_subr_1o:
  1345.     return SUBRF (proc) (t.arg1);
  1346.       case tc7_cxr:
  1347. #ifdef FLOATS
  1348.     if (SUBRF (proc))
  1349.       {
  1350.         if (INUMP (t.arg1))
  1351.         return scm_makdbl (DSUBRF (proc) ((double) INUM (t.arg1)),
  1352.                    0.0);
  1353.         ASRTGO (NIMP (t.arg1), floerr);
  1354.         if (REALP (t.arg1))
  1355.         return scm_makdbl (DSUBRF (proc) (REALPART (t.arg1)), 0.0);
  1356. #ifdef BIGDIG
  1357.         if (BIGP (t.arg1))
  1358.         return scm_makdbl (DSUBRF (proc) (scm_big2dbl (t.arg1)), 0.0);
  1359. #endif
  1360.       floerr:
  1361.         scm_wta (t.arg1, (char *) ARG1, CHARS (SNAME (proc)));
  1362.       }
  1363. #endif
  1364.     proc = (SCM) SNAME (proc);
  1365.     {
  1366.       char *chrs = CHARS (proc) + LENGTH (proc) - 1;
  1367.       while ('c' != *--chrs)
  1368.         {
  1369.           ASSERT (NIMP (t.arg1) && CONSP (t.arg1),
  1370.               t.arg1, ARG1, CHARS (proc));
  1371.           t.arg1 = ('a' == *chrs) ? CAR (t.arg1) : CDR (t.arg1);
  1372.         }
  1373.       return t.arg1;
  1374.     }
  1375.       case tc7_rpsubr:
  1376.     return BOOL_T;
  1377.       case tc7_asubr:
  1378.     return SUBRF (proc) (t.arg1, SCM_UNDEFINED);
  1379.       case tc7_lsubr:
  1380.     return SUBRF (proc) (scm_cons (t.arg1, EOL));
  1381. #ifdef CCLO
  1382.       case tc7_cclo:
  1383.     arg2 = t.arg1;
  1384.     t.arg1 = proc;
  1385.     proc = CCLO_SUBR (proc);
  1386.     goto evap2;
  1387. #endif
  1388.       case tcs_closures:
  1389.     x = CODE (proc);
  1390.     env = EXTEND_ENV (CAR (x), scm_cons (t.arg1, EOL), ENV (proc));
  1391.     goto cdrxbegin;
  1392.       case tc7_contin:
  1393.     scm_throw (proc, t.arg1);
  1394.       case tc7_subr_2:
  1395.       case tc7_subr_0:
  1396.       case tc7_subr_3:
  1397.       case tc7_lsubr_2:
  1398.     goto wrongnumargs;
  1399.       default:
  1400.     goto badfun;
  1401.       }
  1402. #ifdef CAUTIOUS
  1403.   if (IMP (x))
  1404.     goto wrongnumargs;
  1405. #endif
  1406.   {                /* have two or more arguments */
  1407.     arg2 = EVALCAR (x, env);
  1408.     x = CDR (x);
  1409.     if (NULLP (x))
  1410. #ifdef CCLO
  1411.     evap2:
  1412. #endif
  1413.       switch TYP7
  1414.     (proc)
  1415.     {            /* have two arguments */
  1416.     case tc7_subr_2:
  1417.     case tc7_subr_2o:
  1418.       return SUBRF (proc) (t.arg1, arg2);
  1419.     case tc7_lsubr:
  1420.       return SUBRF (proc) (scm_cons2 (t.arg1, arg2, EOL));
  1421.     case tc7_lsubr_2:
  1422.       return SUBRF (proc) (t.arg1, arg2, EOL);
  1423.     case tc7_rpsubr:
  1424.     case tc7_asubr:
  1425.       return SUBRF (proc) (t.arg1, arg2);
  1426. #ifdef CCLO
  1427.     cclon: case tc7_cclo:
  1428.       return scm_apply (CCLO_SUBR (proc), proc,
  1429.       scm_cons2 (t.arg1, arg2, scm_cons (scm_eval_args (x, env), EOL)));
  1430. /*    case tc7_cclo:
  1431.       x = scm_cons(arg2, scm_eval_args(x, env));
  1432.       arg2 = t.arg1;
  1433.       t.arg1 = proc;
  1434.       proc = CCLO_SUBR(proc);
  1435.       goto evap3; */
  1436. #endif
  1437.     case tc7_subr_0:
  1438.     case tc7_cxr:
  1439.     case tc7_subr_1o:
  1440.     case tc7_subr_1:
  1441.     case tc7_subr_3:
  1442.     case tc7_contin:
  1443.       goto wrongnumargs;
  1444.     default:
  1445.       goto badfun;
  1446.     case tcs_closures:
  1447.       env = EXTEND_ENV (CAR (CODE (proc)), scm_cons2 (t.arg1, arg2, EOL), ENV (proc));
  1448.       x = CODE (proc);
  1449.       goto cdrxbegin;
  1450.     }
  1451.     switch TYP7
  1452.       (proc)
  1453.       {                /* have 3 or more arguments */
  1454.       case tc7_subr_3:
  1455.     ASRTGO (NULLP (CDR (x)), wrongnumargs);
  1456.     return SUBRF (proc) (t.arg1, arg2, EVALCAR (x, env));
  1457.       case tc7_asubr:
  1458. /*      t.arg1 = SUBRF(proc)(t.arg1, arg2);
  1459.       while NIMP(x) {
  1460.     t.arg1 = SUBRF(proc)(t.arg1, EVALCAR(x, env));
  1461.     x = CDR(x);
  1462.       }
  1463.       return t.arg1; */
  1464.       case tc7_rpsubr:
  1465.     return scm_apply (proc, t.arg1, scm_acons (arg2, scm_eval_args (x, env), EOL));
  1466.       case tc7_lsubr_2:
  1467.     return SUBRF (proc) (t.arg1, arg2, scm_eval_args (x, env));
  1468.       case tc7_lsubr:
  1469.     return SUBRF (proc) (scm_cons2 (t.arg1, arg2, scm_eval_args (x, env)));
  1470. #ifdef CCLO
  1471.       case tc7_cclo:
  1472.     goto cclon;
  1473. #endif
  1474.       case tcs_closures:
  1475.     env = EXTEND_ENV (CAR (CODE (proc)),
  1476.               scm_cons2 (t.arg1, arg2, scm_eval_args (x, env)),
  1477.               ENV (proc));
  1478.     x = CODE (proc);
  1479.     goto cdrxbegin;
  1480.       case tc7_subr_2:
  1481.       case tc7_subr_1o:
  1482.       case tc7_subr_2o:
  1483.       case tc7_subr_0:
  1484.       case tc7_cxr:
  1485.       case tc7_subr_1:
  1486.       case tc7_contin:
  1487.     goto wrongnumargs;
  1488.       default:
  1489.     goto badfun;
  1490.       }
  1491.   }
  1492. }
  1493.  
  1494.  
  1495.  
  1496. PROC (s_procedure_documentation, "procedure-documentation", 1, 0, 0, scm_procedure_documentation);
  1497. #ifdef __STDC__
  1498. SCM 
  1499. scm_procedure_documentation (SCM proc)
  1500. #else
  1501. SCM 
  1502. scm_procedure_documentation (proc)
  1503.      SCM proc;
  1504. #endif
  1505. {
  1506.   SCM code;
  1507.   ASSERT (BOOL_T == scm_procedurep (proc) && NIMP (proc) && TYP7 (proc) != tc7_contin,
  1508.       proc, ARG1, s_procedure_documentation);
  1509.   switch (TYP7 (proc))
  1510.     {
  1511.     case tcs_closures:
  1512.       code = CDR (CODE (proc));
  1513.       if (IMP (CDR (code)))
  1514.     return BOOL_F;
  1515.       code = CAR (code);
  1516.       if (IMP (code))
  1517.     return BOOL_F;
  1518.       if (STRINGP (code))
  1519.     return code;
  1520.     default:
  1521.       return BOOL_F;
  1522. /*
  1523.   case tcs_subrs:
  1524. #ifdef CCLO
  1525.   case tc7_cclo:
  1526. #endif
  1527. */
  1528.     }
  1529. }
  1530.  
  1531. /* This code is for scm_apply. it is destructive on multiple args.
  1532.  * This will only screw you if you do (scm_apply scm_apply '( ... )) 
  1533.  */
  1534. PROC (s_nconc2last, "apply:nconc2last", 1, 0, 0, scm_nconc2last);
  1535. #ifdef __STDC__
  1536. SCM 
  1537. scm_nconc2last (SCM lst)
  1538. #else
  1539. SCM 
  1540. scm_nconc2last (lst)
  1541.      SCM lst;
  1542. #endif
  1543. {
  1544.   SCM *lloc = &lst;
  1545.   while (NNULLP (CDR (*lloc)))
  1546.     lloc = &CDR (*lloc);
  1547.   *lloc = CAR (*lloc);
  1548.   return lst;
  1549. }
  1550.  
  1551.  
  1552. #ifdef __STDC__
  1553. SCM 
  1554. scm_apply (SCM proc, SCM arg1, SCM args)
  1555. #else
  1556. SCM 
  1557. scm_apply (proc, arg1, args)
  1558.      SCM proc;
  1559.      SCM arg1;
  1560.      SCM args;
  1561. #endif
  1562. {
  1563.   ASRTGO (NIMP (proc), badproc);
  1564.   if (NULLP (args))
  1565.     if (NULLP (arg1))
  1566.       arg1 = SCM_UNDEFINED;
  1567.     else
  1568.       {
  1569.     args = CDR (arg1);
  1570.     arg1 = CAR (arg1);
  1571.       }
  1572.   else
  1573.     {
  1574.       /*        ASRTGO(NIMP(args) && CONSP(args), wrongnumargs); */
  1575.       args = scm_nconc2last (args);
  1576.     }
  1577. #ifdef CCLO
  1578. tail:
  1579. #endif
  1580.   switch (TYP7 (proc))
  1581.     {
  1582.     case tc7_subr_2o:
  1583.       args = NULLP (args) ? SCM_UNDEFINED : CAR (args);
  1584.       return SUBRF (proc) (arg1, args);
  1585.     case tc7_subr_2:
  1586.       ASRTGO (NULLP (CDR (args)), wrongnumargs);
  1587.       args = CAR (args);
  1588.       return SUBRF (proc) (arg1, args);
  1589.     case tc7_subr_0:
  1590.       ASRTGO (UNBNDP (arg1), wrongnumargs);
  1591.       return SUBRF (proc) ();
  1592.     case tc7_subr_1:
  1593.     case tc7_subr_1o:
  1594.       ASRTGO (NULLP (args), wrongnumargs);
  1595.       return SUBRF (proc) (arg1);
  1596.     case tc7_cxr:
  1597.       ASRTGO (NULLP (args), wrongnumargs);
  1598. #ifdef FLOATS
  1599.       if (SUBRF (proc))
  1600.     {
  1601.       if INUMP
  1602.         (arg1)
  1603.           return scm_makdbl (DSUBRF (proc) ((double) INUM (arg1)), 0.0);
  1604.       ASRTGO (NIMP (arg1), floerr);
  1605.       if REALP
  1606.         (arg1)
  1607.           return scm_makdbl (DSUBRF (proc) (REALPART (arg1)), 0.0);
  1608. #ifdef BIGDIG
  1609.       if BIGP
  1610.         (arg1)
  1611.           return scm_makdbl (DSUBRF (proc) (scm_big2dbl (arg1)), 0.0);
  1612. #endif
  1613.     floerr:
  1614.       scm_wta (arg1, (char *) ARG1, CHARS (SNAME (proc)));
  1615.     }
  1616. #endif
  1617.       proc = (SCM) SNAME (proc);
  1618.       {
  1619.     char *chrs = CHARS (proc) + LENGTH (proc) - 1;
  1620.     while ('c' != *--chrs)
  1621.       {
  1622.         ASSERT (NIMP (arg1) && CONSP (arg1),
  1623.             arg1, ARG1, CHARS (proc));
  1624.         arg1 = ('a' == *chrs) ? CAR (arg1) : CDR (arg1);
  1625.       }
  1626.     return arg1;
  1627.       }
  1628.     case tc7_subr_3:
  1629.       return SUBRF (proc) (arg1, CAR (args), CAR (CDR (args)));
  1630.     case tc7_lsubr:
  1631.       return SUBRF (proc) (UNBNDP (arg1) ? EOL : scm_cons (arg1, args));
  1632.     case tc7_lsubr_2:
  1633.       ASRTGO (NIMP (args) && CONSP (args), wrongnumargs);
  1634.       return SUBRF (proc) (arg1, CAR (args), CDR (args));
  1635.     case tc7_asubr:
  1636.       if (NULLP (args))
  1637.     return SUBRF (proc) (arg1, SCM_UNDEFINED);
  1638.       while (NIMP (args))
  1639.     {
  1640.       ASSERT (CONSP (args), args, ARG2, "apply");
  1641.       arg1 = SUBRF (proc) (arg1, CAR (args));
  1642.       args = CDR (args);
  1643.     }
  1644.       return arg1;
  1645.     case tc7_rpsubr:
  1646.       if (NULLP (args))
  1647.     return BOOL_T;
  1648.       while (NIMP (args))
  1649.     {
  1650.       ASSERT (CONSP (args), args, ARG2, "apply");
  1651.       if FALSEP
  1652.         (SUBRF (proc) (arg1, CAR (args))) return BOOL_F;
  1653.       arg1 = CAR (args);
  1654.       args = CDR (args);
  1655.     }
  1656.       return BOOL_T;
  1657.     case tcs_closures:
  1658.       arg1 = (UNBNDP (arg1) ? EOL : scm_cons (arg1, args));
  1659. #ifndef RECKLESS
  1660.       if (scm_badargsp (CAR (CODE (proc)), arg1))
  1661.     goto wrongnumargs;
  1662. #endif
  1663.       args = EXTEND_ENV (CAR (CODE (proc)), arg1, ENV (proc));
  1664.       proc = CODE (proc);
  1665.       while (NNULLP (proc = CDR (proc)))
  1666.     arg1 = EVALCAR (proc, args);
  1667.       return arg1;
  1668.     case tc7_contin:
  1669.       ASRTGO (NULLP (args), wrongnumargs);
  1670.       scm_throw (proc, arg1);
  1671. #ifdef CCLO
  1672.     case tc7_cclo:
  1673.       args = (UNBNDP(arg1) ? EOL : scm_cons (arg1, args));
  1674.       arg1 = proc;
  1675.       proc = CCLO_SUBR (proc);
  1676.       goto tail;
  1677. #endif
  1678.     wrongnumargs:
  1679.       scm_wta (proc, (char *) WNA, "apply");
  1680.     default:
  1681.     badproc:
  1682.       scm_wta (proc, (char *) ARG1, "apply");
  1683.       return arg1;
  1684.     }
  1685. }
  1686.  
  1687.  
  1688. PROC (s_map, "map", 2, 0, 1, scm_map);
  1689. #ifdef __STDC__
  1690. SCM 
  1691. scm_map (SCM proc, SCM arg1, SCM args)
  1692. #else
  1693. SCM 
  1694. scm_map (proc, arg1, args)
  1695.      SCM proc;
  1696.      SCM arg1;
  1697.      SCM args;
  1698. #endif
  1699. {
  1700.   long i;
  1701.   SCM res = EOL;
  1702.   SCM *pres = &res;
  1703.   SCM *ve = &args;        /* Keep args from being optimized away. */
  1704.  
  1705.   if (NULLP (arg1))
  1706.     return res;
  1707.   ASSERT (NIMP (arg1), arg1, ARG2, s_map);
  1708.   if (NULLP (args))
  1709.     {
  1710.       while (NIMP (arg1))
  1711.     {
  1712.       ASSERT (CONSP (arg1), arg1, ARG2, s_map);
  1713.       *pres = scm_cons (scm_apply (proc, CAR (arg1), listofnull), EOL);
  1714.       pres = &CDR (*pres);
  1715.       arg1 = CDR (arg1);
  1716.     }
  1717.       return res;
  1718.     }
  1719.   args = scm_vector (scm_cons (arg1, args));
  1720.   ve = VELTS (args);
  1721. #ifndef RECKLESS
  1722.   for (i = LENGTH (args) - 1; i >= 0; i--)
  1723.     ASSERT (NIMP (ve[i]) && CONSP (ve[i]), args, ARG2, s_map);
  1724. #endif
  1725.   while (1)
  1726.     {
  1727.       arg1 = EOL;
  1728.       for (i = LENGTH (args) - 1; i >= 0; i--)
  1729.     {
  1730.       if IMP
  1731.         (ve[i]) return res;
  1732.       arg1 = scm_cons (CAR (ve[i]), arg1);
  1733.       ve[i] = CDR (ve[i]);
  1734.     }
  1735.       *pres = scm_cons (scm_apply (proc, arg1, EOL), EOL);
  1736.       pres = &CDR (*pres);
  1737.     }
  1738. }
  1739.  
  1740.  
  1741. PROC (s_for_each, "for-each", 2, 0, 1, scm_for_each);
  1742. #ifdef __STDC__
  1743. SCM 
  1744. scm_for_each (SCM proc, SCM arg1, SCM args)
  1745. #else
  1746. SCM 
  1747. scm_for_each (proc, arg1, args)
  1748.      SCM proc;
  1749.      SCM arg1;
  1750.      SCM args;
  1751. #endif
  1752. {
  1753.   SCM *ve = &args;        /* Keep args from being optimized away. */
  1754.   long i;
  1755.   if NULLP (arg1)
  1756.     return UNSPECIFIED;
  1757.   ASSERT (NIMP (arg1), arg1, ARG2, s_for_each);
  1758.   if NULLP (args)
  1759.     {
  1760.       while NIMP (arg1)
  1761.     {
  1762.       ASSERT (CONSP (arg1), arg1, ARG2, s_for_each);
  1763.       scm_apply (proc, CAR (arg1), listofnull);
  1764.       arg1 = CDR (arg1);
  1765.     }
  1766.       return UNSPECIFIED;
  1767.     }
  1768.   args = scm_vector (scm_cons (arg1, args));
  1769.   ve = VELTS (args);
  1770. #ifndef RECKLESS
  1771.   for (i = LENGTH (args) - 1; i >= 0; i--)
  1772.     ASSERT (NIMP (ve[i]) && CONSP (ve[i]), args, ARG2, s_for_each);
  1773. #endif
  1774.   while (1)
  1775.     {
  1776.       arg1 = EOL;
  1777.       for (i = LENGTH (args) - 1; i >= 0; i--)
  1778.     {
  1779.       if IMP
  1780.         (ve[i]) return UNSPECIFIED;
  1781.       arg1 = scm_cons (CAR (ve[i]), arg1);
  1782.       ve[i] = CDR (ve[i]);
  1783.     }
  1784.       scm_apply (proc, arg1, EOL);
  1785.     }
  1786. }
  1787.  
  1788.  
  1789. #ifdef __STDC__
  1790. SCM 
  1791. scm_closure (SCM code, SCM env)
  1792. #else
  1793. SCM 
  1794. scm_closure (code, env)
  1795.      SCM code;
  1796.      SCM env;
  1797. #endif
  1798. {
  1799.   register SCM z;
  1800.   NEWCELL (z);
  1801.   SETCODE (z, code);
  1802.   ENV (z) = env;
  1803.   return z;
  1804. }
  1805.  
  1806.  
  1807. long scm_tc16_promise;
  1808. #ifdef __STDC__
  1809. SCM 
  1810. scm_makprom (SCM code)
  1811. #else
  1812. SCM 
  1813. scm_makprom (code)
  1814.      SCM code;
  1815. #endif
  1816. {
  1817.   register SCM z;
  1818.   NEWCELL (z);
  1819.   CDR (z) = code;
  1820.   CAR (z) = scm_tc16_promise;
  1821.   return z;
  1822. }
  1823.  
  1824.  
  1825. #ifdef __STDC__
  1826. static int 
  1827. prinprom (SCM exp, SCM port, int writing)
  1828. #else
  1829. static int 
  1830. prinprom (exp, port, writing)
  1831.      SCM exp;
  1832.      SCM port;
  1833.      int writing;
  1834. #endif
  1835. {
  1836.   scm_puts ("#<promise ", port);
  1837.   scm_iprin1 (CDR (exp), port, writing);
  1838.   scm_putc ('>', port);
  1839.   return !0;
  1840. }
  1841.  
  1842.  
  1843. PROC (s_makacro, "procedure->syntax", 1, 0, 0, scm_makacro);
  1844. #ifdef __STDC__
  1845. SCM 
  1846. scm_makacro (SCM code)
  1847. #else
  1848. SCM 
  1849. scm_makacro (code)
  1850.      SCM code;
  1851. #endif
  1852. {
  1853.   register SCM z;
  1854.   NEWCELL (z);
  1855.   CDR (z) = code;
  1856.   CAR (z) = scm_tc16_macro;
  1857.   return z;
  1858. }
  1859.  
  1860.  
  1861. PROC (s_makmacro, "procedure->macro", 1, 0, 0, scm_makmacro);
  1862. #ifdef __STDC__
  1863. SCM 
  1864. scm_makmacro (SCM code)
  1865. #else
  1866. SCM 
  1867. scm_makmacro (code)
  1868.      SCM code;
  1869. #endif
  1870. {
  1871.   register SCM z;
  1872.   NEWCELL (z);
  1873.   CDR (z) = code;
  1874.   CAR (z) = scm_tc16_macro | (1L << 16);
  1875.   return z;
  1876. }
  1877.  
  1878.  
  1879. PROC (s_makmmacro, "procedure->memoizing-macro", 1, 0, 0, scm_makmmacro);
  1880. #ifdef __STDC__
  1881. SCM 
  1882. scm_makmmacro (SCM code)
  1883. #else
  1884. SCM 
  1885. scm_makmmacro (code)
  1886.      SCM code;
  1887. #endif
  1888. {
  1889.   register SCM z;
  1890.   NEWCELL (z);
  1891.   CDR (z) = code;
  1892.   CAR (z) = scm_tc16_macro | (2L << 16);
  1893.   return z;
  1894. }
  1895.  
  1896.  
  1897. #ifdef __STDC__
  1898. static int 
  1899. prinmacro (SCM exp, SCM port, int writing)
  1900. #else
  1901. static int 
  1902. prinmacro (exp, port, writing)
  1903.      SCM exp;
  1904.      SCM port;
  1905.      int writing;
  1906. #endif
  1907. {
  1908.   if (CAR (exp) & (3L << 16))
  1909.     scm_puts ("#<macro", port);
  1910.   else
  1911.     scm_puts ("#<syntax", port);
  1912.   if (CAR (exp) & (2L << 16))
  1913.     scm_putc ('!', port);
  1914.   scm_putc (' ', port);
  1915.   scm_iprin1 (CDR (exp), port, writing);
  1916.   scm_putc ('>', port);
  1917.   return !0;
  1918. }
  1919.  
  1920. PROC (s_force, "force", 1, 0, 0, scm_force);
  1921. #ifdef __STDC__
  1922. SCM 
  1923. scm_force (SCM x)
  1924. #else
  1925. SCM 
  1926. scm_force (x)
  1927.      SCM x;
  1928. #endif
  1929. {
  1930.   ASSERT ((TYP16 (x) == scm_tc16_promise), x, ARG1, s_force);
  1931.   if (!((1L << 16) & CAR (x)))
  1932.     {
  1933.       SCM ans = scm_apply (CDR (x), EOL, EOL);
  1934.       if (!((1L << 16) & CAR (x)))
  1935.     {
  1936.       DEFER_INTS;
  1937.       CDR (x) = ans;
  1938.       CAR (x) |= (1L << 16);
  1939.       ALLOW_INTS;
  1940.     }
  1941.     }
  1942.   return CDR (x);
  1943. }
  1944.  
  1945. PROC (s_copy_tree, "copy-tree", 1, 0, 0, scm_copy_tree);
  1946. #ifdef __STDC__
  1947. SCM 
  1948. scm_copy_tree (SCM obj)
  1949. #else
  1950. SCM 
  1951. scm_copy_tree (obj)
  1952.      SCM obj;
  1953. #endif
  1954. {
  1955.   SCM ans, tl;
  1956.   if IMP
  1957.     (obj) return obj;
  1958.   if VECTORP
  1959.     (obj)
  1960.     {
  1961.       sizet i = LENGTH (obj);
  1962.       ans = scm_make_vector (MAKINUM (i), UNSPECIFIED);
  1963.       while (i--)
  1964.     VELTS (ans)[i] = scm_copy_tree (VELTS (obj)[i]);
  1965.       return ans;
  1966.     }
  1967.   if NCONSP (obj)
  1968.     return obj;
  1969. /*  return scm_cons(scm_copy_tree(CAR(obj)), scm_copy_tree(CDR(obj))); */
  1970.   ans = tl = scm_cons (scm_copy_tree (CAR (obj)), UNSPECIFIED);
  1971.   while (NIMP (obj = CDR (obj)) && CONSP (obj))
  1972.     tl = (CDR (tl) = scm_cons (scm_copy_tree (CAR (obj)), UNSPECIFIED));
  1973.   CDR (tl) = obj;
  1974.   return ans;
  1975. }
  1976.  
  1977. static SCM system_transformer;
  1978.  
  1979. #ifdef __STDC__
  1980. SCM 
  1981. scm_eval_3 (SCM obj, int copyp, SCM env)
  1982. #else
  1983. SCM 
  1984. scm_eval_3 (obj, copyp, env)
  1985.      SCM obj;
  1986.      int copyp;
  1987.      SCM env;
  1988. #endif
  1989. {
  1990.   if (NIMP (CDR (system_transformer)))
  1991.     obj = scm_apply (CDR (system_transformer), obj, listofnull);
  1992.   else if (copyp)
  1993.     obj = scm_copy_tree (obj);
  1994.   return IMP(obj) ? obj : scm_ceval (obj, env);
  1995. }
  1996.  
  1997. #ifdef __STDC__
  1998. SCM
  1999. scm_top_level_env (SCM thunk)
  2000. #else
  2001. SCM
  2002. scm_top_level_env (thunk)
  2003.      SCM thunk;
  2004. #endif
  2005. {
  2006.   if (IMP(thunk))
  2007.     return EOL;
  2008.   else
  2009.     return scm_cons(thunk, (SCM)EOL);
  2010. }
  2011.  
  2012. PROC (s_eval2, "eval2", 2, 0, 0, scm_eval2);
  2013. #ifdef __STDC__
  2014. SCM
  2015. scm_eval2 (SCM obj, SCM env_thunk)
  2016. #else
  2017. SCM
  2018. scm_eval2 (obj, env_thunk)
  2019.      SCM obj;
  2020.      SCM env_thunk;
  2021. #endif
  2022. {
  2023.   return scm_eval_3 (obj, 1, scm_top_level_env(env_thunk));
  2024. }
  2025.  
  2026. PROC (s_eval, "eval", 1, 0, 0, scm_eval);
  2027. #ifdef __STDC__
  2028. SCM
  2029. scm_eval (SCM obj)
  2030. #else
  2031. SCM
  2032. scm_eval (obj)
  2033.      SCM obj;
  2034. #endif
  2035. {
  2036.   return
  2037.     scm_eval_3(obj, 1, scm_top_level_env(CDR(scm_top_level_lookup_thunk_var)));
  2038. }
  2039.  
  2040. PROC (s_eval_x, "eval!", 1, 0, 0, scm_eval_x);
  2041. #ifdef __STDC__
  2042. SCM
  2043. scm_eval_x (SCM obj)
  2044. #else
  2045. SCM
  2046. scm_eval_x (obj)
  2047.      SCM obj;
  2048. #endif
  2049. {
  2050.   return
  2051.     scm_eval_3(obj,
  2052.            0,
  2053.            scm_top_level_env (CDR (scm_top_level_lookup_thunk_var)));
  2054. }
  2055.  
  2056. #ifdef __STDC__
  2057. SCM 
  2058. scm_definedp (SCM x, SCM env)
  2059. #else
  2060. SCM 
  2061. scm_definedp (x, env)
  2062.      SCM x;
  2063.      SCM env;
  2064. #endif
  2065. {
  2066.   SCM proc = CAR (x = CDR (x));
  2067.   if (ISYMP (proc))
  2068.     return BOOL_T;
  2069.   else if(IMP(proc) || !SYMBOLP(proc))
  2070.     return BOOL_F;
  2071.   else
  2072.     {
  2073.       SCM vcell = scm_sym2vcell(proc, env_top_level(env), BOOL_F);
  2074.       return (vcell == BOOL_F || UNBNDP(CDR(vcell))) ? BOOL_F : BOOL_T;
  2075.     }
  2076. }
  2077.  
  2078. static scm_smobfuns promsmob =
  2079. {scm_markcdr, scm_free0, prinprom};
  2080.  
  2081. static scm_smobfuns macrosmob =
  2082. {scm_markcdr, scm_free0, prinmacro};
  2083.  
  2084. #ifdef __STDC__
  2085. SCM 
  2086. scm_make_synt (char *name, SCM (*macroizer) (), SCM (*fcn) ())
  2087. #else
  2088. SCM 
  2089. scm_make_synt (name, macroizer, fcn)
  2090.      char *name;
  2091.      SCM (*macroizer) ();
  2092.      SCM (*fcn) ();
  2093. #endif
  2094. {
  2095.   SCM symcell = scm_sysintern (name, SCM_UNDEFINED);
  2096.   long tmp = ((((CELLPTR) (CAR (symcell))) - scm_heap_org) << 8);
  2097.   register SCM z;
  2098.   if ((tmp >> 8) != ((CELLPTR) (CAR (symcell)) - scm_heap_org))
  2099.     tmp = 0;
  2100.   NEWCELL (z);
  2101.   SUBRF (z) = fcn;
  2102.   CAR (z) = tmp + tc7_subr_2;
  2103.   CDR (symcell) = macroizer (z);
  2104.   return CAR (symcell);
  2105. }
  2106.  
  2107.  
  2108. #ifdef __STDC__
  2109. void 
  2110. scm_init_eval (void)
  2111. #else
  2112. void 
  2113. scm_init_eval ()
  2114. #endif
  2115. {
  2116.   scm_tc16_promise = scm_newsmob (&promsmob);
  2117.   scm_tc16_macro = scm_newsmob (¯osmob);
  2118.   scm_i_apply = scm_make_subr ("apply", tc7_lsubr_2, scm_apply);
  2119.   system_transformer = scm_sysintern ("scm:eval-transformer", SCM_UNDEFINED);
  2120.   scm_i_dot = CAR (scm_sysintern (".", SCM_UNDEFINED));
  2121.   scm_i_arrow = CAR (scm_sysintern ("=>", SCM_UNDEFINED));
  2122.   scm_i_else = CAR (scm_sysintern ("else", SCM_UNDEFINED));
  2123.   scm_i_unquote = CAR (scm_sysintern ("unquote", SCM_UNDEFINED));
  2124.   scm_i_uq_splicing = CAR (scm_sysintern ("unquote-splicing", SCM_UNDEFINED));
  2125.  
  2126.   /* acros */
  2127.   scm_i_quasiquote = scm_make_synt (s_quasiquote, scm_makacro, scm_m_quasiquote);
  2128.   scm_make_synt ("define", scm_makmmacro, scm_m_define);
  2129.   scm_make_synt (s_delay, scm_makacro, scm_m_delay);
  2130.   /* end of acros */
  2131.  
  2132.   scm_top_level_lookup_thunk_var =
  2133.     scm_sysintern("*top-level-lookup-thunk*", BOOL_F);
  2134.  
  2135.   scm_make_synt ("and", scm_makmmacro, scm_m_and);
  2136.   scm_make_synt ("begin", scm_makmmacro, scm_m_begin);
  2137.   scm_make_synt ("case", scm_makmmacro, scm_m_case);
  2138.   scm_make_synt ("cond", scm_makmmacro, scm_m_cond);
  2139.   scm_make_synt ("do", scm_makmmacro, scm_m_do);
  2140.   scm_make_synt ("if", scm_makmmacro, scm_m_if);
  2141.   scm_i_lambda = scm_make_synt ("lambda", scm_makmmacro, scm_m_lambda);
  2142.   scm_i_let = scm_make_synt ("let", scm_makmmacro, scm_m_let);
  2143.   scm_make_synt ("letrec", scm_makmmacro, scm_m_letrec);
  2144.   scm_make_synt ("let*", scm_makmmacro, scm_m_letstar);
  2145.   scm_make_synt ("or", scm_makmmacro, scm_m_or);
  2146.   scm_i_quote = scm_make_synt ("quote", scm_makmmacro, scm_m_quote);
  2147.   scm_make_synt ("set!", scm_makmmacro, scm_m_set);
  2148.   scm_make_synt ("@apply", scm_makmmacro, scm_m_apply);
  2149.   scm_make_synt ("@call-with-current-continuation", scm_makmmacro, scm_m_cont);
  2150.   scm_make_synt ("defined?", scm_makmmacro, scm_definedp);
  2151. #include "eval.x"
  2152. }
  2153.